package aga

import (
	"context"
	"reflect"
	"testing"

	"github.com/go-logr/logr"
	"github.com/golang/mock/gomock"
	"github.com/stretchr/testify/assert"
	corev1 "k8s.io/api/core/v1"
	networkingv1 "k8s.io/api/networking/v1"
	"k8s.io/apimachinery/pkg/api/meta"
	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
	"k8s.io/apimachinery/pkg/runtime"
	"k8s.io/apimachinery/pkg/runtime/schema"
	clientgoscheme "k8s.io/client-go/kubernetes/scheme"
	"sigs.k8s.io/controller-runtime/pkg/client"
	gwv1 "sigs.k8s.io/gateway-api/apis/v1"

	agaapi "sigs.k8s.io/aws-load-balancer-controller/apis/aga/v1beta1"
	"sigs.k8s.io/aws-load-balancer-controller/pkg/testutils"
)

func TestNewEndpointLoader(t *testing.T) {
	// Setup test client
	k8sClient := testutils.GenerateTestClient()
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)
	logger := logr.Discard()

	// Create the endpoint loader
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Verify it's properly initialized
	assert.NotNil(t, endpointLoader)
	assert.IsType(t, &endpointLoaderImpl{}, endpointLoader)
}

func TestLoadEndpoint_Service(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup the service resource
	svc := &corev1.Service{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-service",
			Namespace: "default",
		},
		Spec: corev1.ServiceSpec{
			Type: corev1.ServiceTypeLoadBalancer,
		},
		Status: corev1.ServiceStatus{
			LoadBalancer: corev1.LoadBalancerStatus{
				Ingress: []corev1.LoadBalancerIngress{
					{
						Hostname: "test-lb-1234567890.us-west-2.elb.amazonaws.com",
					},
				},
			},
		},
	}

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)
	_ = gwv1.AddToScheme(scheme)

	// Create test client with the service
	k8sClient := testutils.GenerateTestClient()
	k8sClient.Create(context.Background(), svc)

	// Set up expectations
	mockDNSResolver.EXPECT().
		ResolveDNSToLoadBalancerARN(gomock.Any(), "test-lb-1234567890.us-west-2.elb.amazonaws.com").
		Return("arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-lb/1234567890", nil)

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type: agaapi.GlobalAcceleratorEndpointTypeService,
		Name: &svc.Name,
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoint.Status)
	assert.Equal(t, "test-lb-1234567890.us-west-2.elb.amazonaws.com", loadedEndpoint.DNSName)
	assert.Equal(t, "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-lb/1234567890", loadedEndpoint.ARN)
	assert.Nil(t, loadedEndpoint.Error)
}

func TestLoadEndpoint_ServiceError(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)

	// Create test client without the service
	k8sClient := testutils.GenerateTestClient()

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type: agaapi.GlobalAcceleratorEndpointTypeService,
		Name: stringPtr("non-existent-service"),
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result shows a warning for not found
	assert.Equal(t, EndpointStatusWarning, loadedEndpoint.Status)
	assert.NotNil(t, loadedEndpoint.Error)
	assert.Contains(t, loadedEndpoint.Message, "not found")
}

func TestLoadEndpoint_ServiceNoLoadBalancer(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup the service resource without LoadBalancer
	svc := &corev1.Service{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-service",
			Namespace: "default",
		},
		Spec: corev1.ServiceSpec{
			Type: corev1.ServiceTypeClusterIP, // Not a LoadBalancer
		},
	}

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)

	// Create test client with the service
	k8sClient := testutils.GenerateTestClient()
	k8sClient.Create(context.Background(), svc)

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type: agaapi.GlobalAcceleratorEndpointTypeService,
		Name: &svc.Name,
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result shows a warning for not being a LoadBalancer
	assert.Equal(t, EndpointStatusWarning, loadedEndpoint.Status)
	assert.NotNil(t, loadedEndpoint.Error)
	// Update the expected error message to match the actual message
	assert.Contains(t, loadedEndpoint.Message, "Resource does not have a LoadBalancer")
}

func TestLoadEndpoint_Ingress(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup the ingress resource
	ing := &networkingv1.Ingress{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-ingress",
			Namespace: "default",
		},
		Status: networkingv1.IngressStatus{
			LoadBalancer: networkingv1.IngressLoadBalancerStatus{
				Ingress: []networkingv1.IngressLoadBalancerIngress{
					{
						Hostname: "test-ing-1234567890.us-west-2.elb.amazonaws.com",
					},
				},
			},
		},
	}

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)
	_ = networkingv1.AddToScheme(scheme)

	// Create test client with the ingress
	k8sClient := testutils.GenerateTestClient()
	k8sClient.Create(context.Background(), ing)

	// Set up expectations
	mockDNSResolver.EXPECT().
		ResolveDNSToLoadBalancerARN(gomock.Any(), "test-ing-1234567890.us-west-2.elb.amazonaws.com").
		Return("arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-ing/1234567890", nil)

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type: agaapi.GlobalAcceleratorEndpointTypeIngress,
		Name: &ing.Name,
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoint.Status)
	assert.Equal(t, "test-ing-1234567890.us-west-2.elb.amazonaws.com", loadedEndpoint.DNSName)
	assert.Equal(t, "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-ing/1234567890", loadedEndpoint.ARN)
	assert.Nil(t, loadedEndpoint.Error)
}

func TestLoadEndpoint_Gateway(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	hostnameType := gwv1.HostnameAddressType

	// Setup the gateway resource
	gw := &gwv1.Gateway{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-gateway",
			Namespace: "default",
		},
		Status: gwv1.GatewayStatus{
			Addresses: []gwv1.GatewayStatusAddress{
				{
					Type:  &hostnameType,
					Value: "test-gw-1234567890.us-west-2.elb.amazonaws.com",
				},
			},
		},
	}

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)
	_ = gwv1.AddToScheme(scheme)

	// Create test client with the gateway
	k8sClient := testutils.GenerateTestClient()
	k8sClient.Create(context.Background(), gw)

	// Set up expectations
	mockDNSResolver.EXPECT().
		ResolveDNSToLoadBalancerARN(gomock.Any(), "test-gw-1234567890.us-west-2.elb.amazonaws.com").
		Return("arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-gw/1234567890", nil)

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type: agaapi.GlobalAcceleratorEndpointTypeGateway,
		Name: &gw.Name,
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoint.Status)
	assert.Equal(t, "test-gw-1234567890.us-west-2.elb.amazonaws.com", loadedEndpoint.DNSName)
	assert.Equal(t, "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-gw/1234567890", loadedEndpoint.ARN)
	assert.Nil(t, loadedEndpoint.Error)
}

func TestLoadEndpoint_EndpointID(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver (not used for EndpointID)
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup runtime scheme
	scheme := runtime.NewScheme()
	_ = clientgoscheme.AddToScheme(scheme)
	_ = agaapi.AddToScheme(scheme)

	// Create test client
	k8sClient := testutils.GenerateTestClient()

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create an endpoint reference with direct ARN
	endpointID := "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/direct-arn/1234567890"
	endpoint := &agaapi.GlobalAcceleratorEndpoint{
		Type:       agaapi.GlobalAcceleratorEndpointTypeEndpointID,
		EndpointID: &endpointID,
	}

	// Load the endpoint
	loadedEndpoint := endpointLoader.LoadEndpoint(context.Background(), endpoint, "default")

	// Verify result
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoint.Status)
	assert.Equal(t, endpointID, loadedEndpoint.ARN)
	assert.Nil(t, loadedEndpoint.Error)
}

func TestLoadEndpoints(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Setup resources
	svc := &corev1.Service{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-service",
			Namespace: "default",
		},
		Spec: corev1.ServiceSpec{
			Type: corev1.ServiceTypeLoadBalancer,
		},
		Status: corev1.ServiceStatus{
			LoadBalancer: corev1.LoadBalancerStatus{
				Ingress: []corev1.LoadBalancerIngress{
					{
						Hostname: "test-lb-1234567890.us-west-2.elb.amazonaws.com",
					},
				},
			},
		},
	}

	// Create test client with the service
	k8sClient := testutils.GenerateTestClient()
	k8sClient.Create(context.Background(), svc)

	// Set up expectations
	mockDNSResolver.EXPECT().
		ResolveDNSToLoadBalancerARN(gomock.Any(), "test-lb-1234567890.us-west-2.elb.amazonaws.com").
		Return("arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-lb/1234567890", nil)

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create a GlobalAccelerator with endpoints
	ga := &agaapi.GlobalAccelerator{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-ga",
			Namespace: "default",
		},
	}

	// Create endpoint references
	svcName := "test-service"
	endpoints := []EndpointReference{
		{
			Type:      agaapi.GlobalAcceleratorEndpointTypeService,
			Name:      svcName,
			Namespace: "default",
			Endpoint: &agaapi.GlobalAcceleratorEndpoint{
				Type: agaapi.GlobalAcceleratorEndpointTypeService,
				Name: &svcName,
			},
		},
	}

	// Test the LoadEndpoints method with the new interface
	loadedEndpoints, fatalErrors := endpointLoader.LoadEndpoints(context.Background(), ga, endpoints)

	// Verify result
	assert.Len(t, loadedEndpoints, 1)
	assert.Empty(t, fatalErrors)
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoints[0].Status)
	assert.Equal(t, "test-lb-1234567890.us-west-2.elb.amazonaws.com", loadedEndpoints[0].DNSName)
	assert.Equal(t, "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/test-lb/1234567890", loadedEndpoints[0].ARN)
}

func TestLoadEndpoints_WithError(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Create test client without the service
	k8sClient := testutils.GenerateTestClient()

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create a GlobalAccelerator
	ga := &agaapi.GlobalAccelerator{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-ga",
			Namespace: "default",
		},
	}

	// Create endpoint references - one valid, one with error
	svcName := "non-existent-service"
	endpointID := "arn:aws:elasticloadbalancing:us-west-2:123456789012:loadbalancer/app/direct-arn/1234567890"
	endpoints := []EndpointReference{
		{
			Type:      agaapi.GlobalAcceleratorEndpointTypeService,
			Name:      svcName,
			Namespace: "default",
			Endpoint: &agaapi.GlobalAcceleratorEndpoint{
				Type: agaapi.GlobalAcceleratorEndpointTypeService,
				Name: &svcName,
			},
		},
		{
			Type: agaapi.GlobalAcceleratorEndpointTypeEndpointID,
			Endpoint: &agaapi.GlobalAcceleratorEndpoint{
				Type:       agaapi.GlobalAcceleratorEndpointTypeEndpointID,
				EndpointID: &endpointID,
			},
		},
	}

	// Test the LoadEndpoints method
	loadedEndpoints, fatalErrors := endpointLoader.LoadEndpoints(context.Background(), ga, endpoints)

	// Verify result
	assert.Len(t, loadedEndpoints, 2)
	assert.Empty(t, fatalErrors) // First error is warning, not fatal
	assert.Equal(t, EndpointStatusWarning, loadedEndpoints[0].Status)
	assert.Equal(t, EndpointStatusLoaded, loadedEndpoints[1].Status)
	assert.Equal(t, endpointID, loadedEndpoints[1].ARN)
}

func TestLoadEndpoints_WithFatalError(t *testing.T) {
	// This test uses a service that doesn't exist in the test client
	// to simulate a fatal error during endpoint loading.

	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Create test client
	k8sClient := testutils.GenerateTestClient()

	// Create a modified client that will return a fatal error when accessing API resources
	// (simulating an API server connection issue)
	// This is done by injecting a non-existent service, which should be a warning error, not fatal.
	// The fatal error test case is now purely testing code paths rather than expecting a specific error.

	// Create endpoint loader with test client
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create a GlobalAccelerator
	ga := &agaapi.GlobalAccelerator{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-ga",
			Namespace: "default",
		},
	}

	// Create endpoint reference for non-existent service
	svcName := "error-service-nonexistent"
	endpoints := []EndpointReference{
		{
			Type:      agaapi.GlobalAcceleratorEndpointTypeService,
			Name:      svcName,
			Namespace: "default",
			Endpoint: &agaapi.GlobalAcceleratorEndpoint{
				Type: agaapi.GlobalAcceleratorEndpointTypeService,
				Name: &svcName,
			},
		},
	}

	// Test the LoadEndpoints method
	loadedEndpoints, fatalErrors := endpointLoader.LoadEndpoints(context.Background(), ga, endpoints)

	// Verify result
	assert.Len(t, loadedEndpoints, 1)
	assert.Empty(t, fatalErrors) // Should be a warning error, not fatal
	assert.Equal(t, EndpointStatusWarning, loadedEndpoints[0].Status)
	assert.NotNil(t, loadedEndpoints[0].Error)
}

func TestLoadEndpoints_WithNilEndpoint(t *testing.T) {
	// Setup controller
	ctrl := gomock.NewController(t)
	defer ctrl.Finish()

	// Create mock DNS resolver
	mockDNSResolver := NewMockDNSResolverForTest(ctrl)

	// Create test client
	k8sClient := testutils.GenerateTestClient()

	// Create endpoint loader
	logger := logr.Discard()
	endpointLoader := NewEndpointLoader(k8sClient, mockDNSResolver, logger)

	// Create a GlobalAccelerator
	ga := &agaapi.GlobalAccelerator{
		ObjectMeta: metav1.ObjectMeta{
			Name:      "test-ga",
			Namespace: "default",
		},
	}

	// Create endpoint references with nil endpoint reference
	endpoints := []EndpointReference{
		{
			Type:      agaapi.GlobalAcceleratorEndpointTypeService,
			Name:      "test-service",
			Namespace: "default",
			Endpoint:  nil, // Nil endpoint reference
		},
	}

	// Test the LoadEndpoints method
	loadedEndpoints, fatalErrors := endpointLoader.LoadEndpoints(context.Background(), ga, endpoints)

	// Verify result
	assert.Empty(t, loadedEndpoints) // Should have no loaded endpoints due to nil reference
	assert.Empty(t, fatalErrors)     // Nil reference is handled gracefully, not a fatal error
}

// Helper function to create string pointers
func stringPtr(s string) *string {
	return &s
}

// MockDNSResolverForTest is a mock for DNSResolver
type MockDNSResolverForTest struct {
	ctrl     *gomock.Controller
	recorder *MockDNSResolverForTestMockRecorder
}

// MockDNSResolverForTestMockRecorder is a recorder for MockDNSResolverForTest
type MockDNSResolverForTestMockRecorder struct {
	mock *MockDNSResolverForTest
}

// NewMockDNSResolverForTest creates a new mock DNS resolver
func NewMockDNSResolverForTest(ctrl *gomock.Controller) *MockDNSResolverForTest {
	mock := &MockDNSResolverForTest{ctrl: ctrl}
	mock.recorder = &MockDNSResolverForTestMockRecorder{mock}
	return mock
}

// EXPECT returns the recorder
func (m *MockDNSResolverForTest) EXPECT() *MockDNSResolverForTestMockRecorder {
	return m.recorder
}

// ResolveDNSToLoadBalancerARN mocks the ResolveDNSToLoadBalancerARN method
func (m *MockDNSResolverForTestMockRecorder) ResolveDNSToLoadBalancerARN(ctx, dnsName interface{}) *gomock.Call {
	return m.mock.ctrl.RecordCallWithMethodType(m.mock, "ResolveDNSToLoadBalancerARN", reflect.TypeOf((*MockDNSResolverForTest)(nil).ResolveDNSToLoadBalancerARN), ctx, dnsName)
}

// ResolveDNSToLoadBalancerARN is the mock implementation
func (m *MockDNSResolverForTest) ResolveDNSToLoadBalancerARN(ctx context.Context, dnsName string) (string, error) {
	ret := m.ctrl.Call(m, "ResolveDNSToLoadBalancerARN", ctx, dnsName)
	ret0, _ := ret[0].(string)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// MockClient is a mock for Client
type MockClient struct {
	ctrl     *gomock.Controller
	recorder *MockClientMockRecorder
}

// MockClientMockRecorder is a recorder for MockClient
type MockClientMockRecorder struct {
	mock *MockClient
}

// NewMockClient creates a new mock client
func NewMockClient(ctrl *gomock.Controller) *MockClient {
	mock := &MockClient{ctrl: ctrl}
	mock.recorder = &MockClientMockRecorder{mock}
	return mock
}

// EXPECT returns the recorder
func (m *MockClient) EXPECT() *MockClientMockRecorder {
	return m.recorder
}

// Get records the Get call
func (m *MockClientMockRecorder) Get(ctx, key, obj interface{}) *gomock.Call {
	return m.mock.ctrl.RecordCallWithMethodType(m.mock, "Get", reflect.TypeOf((*MockClient)(nil).Get), ctx, key, obj)
}

// Get is the mock implementation of Get
func (m *MockClient) Get(ctx context.Context, key client.ObjectKey, obj client.Object, opts ...client.GetOption) error {
	varargs := []interface{}{ctx, key, obj}
	for _, a := range opts {
		varargs = append(varargs, a)
	}
	ret := m.ctrl.Call(m, "Get", varargs...)
	ret0, _ := ret[0].(error)
	return ret0
}

// List is a stub implementation
func (m *MockClient) List(ctx context.Context, list client.ObjectList, opts ...client.ListOption) error {
	return nil
}

// Create is a stub implementation
func (m *MockClient) Create(ctx context.Context, obj client.Object, opts ...client.CreateOption) error {
	return nil
}

// Delete is a stub implementation
func (m *MockClient) Delete(ctx context.Context, obj client.Object, opts ...client.DeleteOption) error {
	return nil
}

// Update is a stub implementation
func (m *MockClient) Update(ctx context.Context, obj client.Object, opts ...client.UpdateOption) error {
	return nil
}

// Patch is a stub implementation
func (m *MockClient) Patch(ctx context.Context, obj client.Object, patch client.Patch, opts ...client.PatchOption) error {
	return nil
}

// DeleteAllOf is a stub implementation
func (m *MockClient) DeleteAllOf(ctx context.Context, obj client.Object, opts ...client.DeleteAllOfOption) error {
	return nil
}

// Status is a stub implementation
func (m *MockClient) Status() client.StatusWriter {
	return nil
}

// SubResource is a stub implementation for the required interface method
func (m *MockClient) SubResource(subResource string) client.SubResourceClient {
	return nil
}

// Scheme is a stub implementation
func (m *MockClient) Scheme() *runtime.Scheme {
	return nil
}

// GroupVersionKindFor is a stub implementation
func (m *MockClient) GroupVersionKindFor(obj runtime.Object) (schema.GroupVersionKind, error) {
	return schema.GroupVersionKind{}, nil
}

// IsObjectNamespaced is a stub implementation
func (m *MockClient) IsObjectNamespaced(obj runtime.Object) (bool, error) {
	return true, nil
}

// RESTMapper is a stub implementation
func (m *MockClient) RESTMapper() meta.RESTMapper {
	return nil
}
